// 使用编译器来防止头文件被多次包含或重复包含
#pragma once
#include <iostream>
#ifndef COMPLEX_H
#define COMPLEX_H

using namespace std;

class Complex {
public:
    Complex();

    // 默认构造函数, 使用 初始列(initialization) : _real(r), _image(i)
    explicit Complex(const double r = 0, double i = 0) : _real(r), _image(i) {
        cout << "Complex Constructor(" << r << "," << i << ")" << endl;
    }

    Complex(const Complex& x); // copy 构造


    //getter方法
    double getReal() const { return _real; }
    double getImage() const { return _image; }
    //setter方法
    void setReal(double r) { _real = r; }
    void setImage(double i) { _image = i; }


    // 运算符重载
    Complex operator+(const Complex& x) const;

    Complex& operator=(const Complex& x);

    Complex& operator+=(const Complex& x);

    bool operator==(const Complex& x) const;


    //前置 ++i
    Complex& operator++();

    //后置 i++
    Complex operator++(int);


    // 输出流 类似Java toString
    // friend 修饰的函数 能够访问 参数类的私有或受保护成员
    // friend ostream& operator<<(ostream& os, const Complex& x);

    // 输入流 从输入设备读数据 赋值给 Complex对象
    friend istream& operator>>(istream& is, Complex& x);

private:
    double _real;
    double _image;

    Complex& _doPlus(Complex* ths, const Complex& x) {
        this->_real += x._real;
        this->_image += x._image;
        // *this返回一个对象, 不需要关心返回类型是什么,由开发者自己确定.
        // 这里使用 引用类型 接收
        return *this;
    }
};

// 全局函数(非成员函数) 操作符<<
inline ostream& operator<<(ostream& os, const Complex& x) {
    // 需要friend修饰 return os << "(real:" << x._real << ",image:" << x._image << ")" << endl;
    return os << "(real:" << x.getReal() << ",image:" << x.getImage() << ")" <<
           endl;
}

inline istream& operator>>(istream& is, Complex& x) {
    // 默认 空格 或 回车 作为数据分隔
    is >> x._real >> x._image;
    return is;
}


#endif
